                                                                                                                                                                                                                                                                                                                                                                                      #include "mycanvasmaker.h"
#include "log.h"
#include "mapdatahelper.h"
#include "locationdatahelper.h"
#include "toolfun.h"
#include "agvdatahelper.h"
#include <QTimer>
#include "toolfunqt.h"
#include "agvavoidclient.h"
#include "avoidclient.h"
#include "agvavoidudp.h"
#include <QTcpSocket>
#include <QSettings>
#include "customerhelper.h"
#include "outstorehelper.h"
const double stationSize = 1000;


MyCanvasMaker::MyCanvasMaker(QSettings *setting,
                             MapDataHelper *agvDataHelper,
                             LocationDataHelper *locationDataHelper,
                             AgvDataHelper *agvData,
                             AgvAvoidUdp *agvAvoid,
                             AvoidClient *avoidClient,
                             CustomerHelper *customerHelper,
                             OutStoreHelper *outStore,
                             QObject *parent) :
    CanvasMaker(parent),
    _settings(setting),
    _mapData(agvDataHelper),
    _locationData(locationDataHelper),
    _agvData(agvData),
    _agvAvoid(agvAvoid),
    _avoidClient(avoidClient),
    _customerHelper(customerHelper),
    _outStore(outStore)
{
    _showAvoid = 0;
    connect(_locationData, SIGNAL(getStationFlag()), this, SLOT(getStationFun()));
    connect(_locationData, SIGNAL(updateData()), this, SLOT(updateLocation()));
    connect(_agvData, SIGNAL(updateData(int, QStringList, QString)), this, SLOT(updateAgv()));
    connect(_agvAvoid, SIGNAL(update()), this, SLOT(updateAgvAvoid()));
    connect(_avoidClient, SIGNAL(update()), this, SLOT(updateAvoid()));
    _timerTip = createTimer(this, 10000, SLOT(_timerTipFun()), false);
    _isOut = 0;
   // _agvAvoidStr = "75341,-19575,76929,-19558,76876,-14761,75977,-13881,73180,-13911,73197,-15498,73847,-15491,75305,-16275,;";
}

void MyCanvasMaker::paintMap()
{
    _calculateBorder();
    _avoidStr.clear();
    _linesToStr();
    _arcsToStr();
    _queueTextStr.clear();
    _locationStr.clear();
    _locationRectStr.clear();
    _stationStr.clear();
    _stationTextStr.clear();
    if (_locationData->isGetStation())
    {
        logInfo("MyCanvasMaker::paintMap:location str");
        _locationsToStr();
        _queueTextToStr();

    }
    else
    {
        logInfo("MyCanvasMaker::paintMap:station str");
        _stationsToStr();
    }
    setUpdateFlag();

}

void MyCanvasMaker::onClick(double x, double y)
{
    logInfo("MyCanvasMaker::onClick:x=%lf,y=%lf", x, y);
    if (_isOut)
    {
        int ret = _outStore->onClick(x, y);
        if (ret)
        {
            repaint();
        }
        return;
    }
    logInfo("MyCanvasMaker::onClick:x=%lf,y=%lf,222", x, y);
    if (_findInAgv(x,y))
    {
       // return;
    }
    if (_findInStation(x,y))
    {
        repaint();
        return;
    }
    else
    {
        _tipStr = "";
        repaint();
    }
}


QString MyCanvasMaker::mapLines()
{
    return _mapLines;
}

QString MyCanvasMaker::mapArcs()
{
    return _mapArcs;
}

QString MyCanvasMaker::stations()
{
    return _stationStr;
}

QString MyCanvasMaker::locations()
{
    return _locationStr;
}

QString MyCanvasMaker::queueTexts()
{
    return _queueTextStr;
}

QString MyCanvasMaker::zoneTitles()
{
    return _customerHelper->zoneTitles;
}

QString MyCanvasMaker::stationTexts()
{
    return _stationTextStr;
}

QString MyCanvasMaker::locationRects()
{
    return _locationRectStr;
}

QString MyCanvasMaker::gridInfoText()
{
    return _gridInfoStr;
}

QString MyCanvasMaker::locationsOut()
{
    return _outStore->mOutLocationStr;
}

QString MyCanvasMaker::agvs()
{
    return _agvStr;
}

QString MyCanvasMaker::tips()
{
    return _tipStr;
}

QString MyCanvasMaker::agvAvoids()
{
    return _agvAvoidStr;
}

QString MyCanvasMaker::avoids()
{
    return _avoidStr;
}

QString MyCanvasMaker::agvAvoidTexts()
{
    //logInfo("MyCanvasMaker::agvAvoidTexts:%s", _agvAvoidTextStr.toUtf8().data());
    return _agvAvoidTextStr;
}

double MyCanvasMaker::stationSize()
{
    return _customerHelper->stationSize;
}

double MyCanvasMaker::agvSize1()
{
    return _customerHelper->agvSize1;
}

double MyCanvasMaker::agvSize2()
{
    return _customerHelper->agvSize2;
}

double MyCanvasMaker::agvSize3()
{
    return _customerHelper->agvSize3;
}

int MyCanvasMaker::showAvoid()
{
    return _showAvoid;
}

void MyCanvasMaker::setShowAvoid(int showAvoid)
{
    logInfo("MyCanvasMaker::setShowAvoi:%d", showAvoid);
    _showAvoid = showAvoid;
    setUpdateFlag();
}

double MyCanvasMaker::agvSizeScale() const
{
    double size = _settings->value("CanvasMaker_agvSizeScale", 1).toDouble();;
   // logInfo("MyCanvasMaker::agvSizeScale:size=%lf", size);
        return size;
}

void MyCanvasMaker::setAgvSizeScale(const double agvSizeScale)
{
   // logInfo("MyCanvasMaker::setAgvSizeScale:size=%lf", agvSizeScale);
    _settings->setValue("CanvasMaker_agvSizeScale", agvSizeScale);
}

void MyCanvasMaker::getStationFun()
{
    //logInfo("MyCanvasMaker::getStationFun");
    _stationStr = "";
    _queueTextToStr();
    _locationsToStr();
    setUpdateFlag();
}

void MyCanvasMaker::updateLocation()
{
    //logInfo("MyCanvasMaker::updateLocation");
    _locationsToStr();
    setUpdateFlag();
}

void MyCanvasMaker::updateAgv()
{
   // logInfo("MyCanvasMaker::updateAgv");
    _agvToStr();
    setUpdateFlag();
}

void MyCanvasMaker::updateAgvAvoid()
{
    _agvAvoidStr = _agvAvoid->areaStr;
    _agvAvoidTextStr = _agvAvoid->textStr;
    setUpdateFlag();
}

void MyCanvasMaker::updateAvoid()
{
    _avoidStr.clear();
     std::vector<QString> &recvMsg  = _avoidClient->mRecvMsg;
    for (int i = 0; i  < recvMsg.size(); i++)
    {
        _avoidStr += recvMsg[i];
    }
    setUpdateFlag();
    logInfo("MyCanvasMaker::updateAvoid:len=%d", _avoidStr.length());
}


void MyCanvasMaker::_timerTipFun()
{
    _timerTip->stop();
    _tipStr = "";
    repaint();
}

void MyCanvasMaker::_linesToStr()
{
    int i;
    logInfo("MyCanvasMaker::_linesToStr:enter");
    QVector<LineData> &lineVector = _mapData->mLineVector;
    _mapLines.clear();
    for (i = 0; i < lineVector.size(); i++)
    {
        LineData &line = lineVector[i];
        QString temp;
        temp.sprintf("%lf,%lf,%lf,%lf,%d;", line.startpoint.x, line.startpoint.y,
                     line.endpoint.x, line.endpoint.y,
                     1 == line.directionality);
        _mapLines += temp;
    }

}

void MyCanvasMaker::_arcsToStr()
{
    QVector<ArcData> &arcVector = _mapData->mArcVector;
    _mapArcs.clear();
    for (int i = 0; i < arcVector.size(); i++)
    {
        ArcData &line = arcVector[i];
        QString temp;
        temp.sprintf("%lf,%lf,%lf,%lf,%lf;", line.arccenter.x, line.arccenter.y,
                     line.radius, line.angle1,line.angle2);
        _mapArcs += temp;
    }
}

void MyCanvasMaker::_stationsToStr()
{
    QVector<StationData> &objVector = _mapData->mStationVector;
    _stationStr.clear();
    _stationTextStr.clear();
    double stationSize = 1000;
    for (int i = 0; i < objVector.size(); i++)
    {
        StationData &line = objVector[i];
        QString temp;
        double min_x = (line.startpoint.x + line.endpoint.x ) / 2 - stationSize / 2;
        double max_y = (line.startpoint.y + line.endpoint.y) / 2 + stationSize / 2;
        temp.sprintf("%d,%lf,%lf,%d;", line.id,
                    min_x,max_y, line.attr);
        _stationStr += temp;

        temp = _customerHelper->getStationText(line.id, min_x, max_y);
        _stationTextStr += temp;
    }
    logInfo("MyCanvasMaker::_stationsToStr:[%s]", _stationStr.toUtf8().data());
}

void MyCanvasMaker::_locationsToStr()
{
    //logInfo("MyCanvasMaker::_locationsToStr:enter");
    _locationStr = "";
    foreach (const share_zone_t &zone, _locationData->mZoneVector) {
        for (int i = 0; i < zone.queue_count; i++)
        {
            const share_queue_t &queue = zone.buf[i];
            for (int j = 0; j < queue.grid_count; j++)
            {
                const share_grid_t &grid = queue.buf[j];
                QString temp = LocationDataHelper::getGridStr(grid);
                _locationStr += temp;
            }
        }

    }
}

void MyCanvasMaker::_queueTextToStr()
{
    _queueTextStr = "";
    _locationRectStr = "";
    foreach (const share_zone_t &zone, _locationData->mZoneVector) {
        for (int i = 0; i < zone.queue_count; i++)
        {
            const share_queue_t &queue = zone.buf[i];
            QString temp = _customerHelper->getQueueText(zone, queue);
            _queueTextStr += temp;

            if (queue.isMultiple)
            {
                temp.sprintf("%lf,%lf,%lf,%lf;", queue.min_x, queue.max_y,
                                             queue.max_x - queue.min_x,
                                             queue.max_y - queue.min_y
                                         );
                _locationRectStr += temp;
            }
        }
    }
}

void MyCanvasMaker::_agvToStr()
{
    //agvStatus.dirangle存的是角度，转换为弧度
    QVector<AgvData> &objVector = _agvData->mAgvVector;
    int selectId = _agvData->getSelectId();
    _agvStr.clear();
    for (int i = 0; i < objVector.size(); i++)
    {
        AgvData &agvStatus = objVector[i];
        QString temp;
        if (selectId == agvStatus.AGV_ID)
        {
            temp.sprintf("%d,%lf,%lf,%lf,1,%d,%d;", agvStatus.AGV_ID, agvStatus.position.x, agvStatus.position.y,
                     agvStatus.dirangle * M_PI/ 180, agvStatus.movedirection, agvStatus.isFull );
        }
        else
        {
            temp.sprintf("%d,%lf,%lf,%lf,0,%d,%d;", agvStatus.AGV_ID, agvStatus.position.x, agvStatus.position.y,
                     agvStatus.dirangle * M_PI/ 180, agvStatus.movedirection, agvStatus.isFull );
        }
        _agvStr += temp;
      //  logInfo("MyCanvasMaker::_agvToStr:%s", temp.toUtf8().data());
    }
}

void _gridInfoToStr(QString &str, const share_zone_t &zone, const share_queue_t &queue, const share_grid_t &grid, int gridId)
{
    str.clear();

    logInfo("ration=%s, name=%s", queue.ration, queue.name);
    str.sprintf("%d,%d,%d,%d,%d,%s,%s,%.4f,"
                "%d,%d,%.2f,%d,%d,"
                "%d,%d,%.2f,%d,%d,"
                "%d,%d,%.2f,%d,%d,"
                "%d,%d,%.2f,%d,%d,"
                "%d,"
                ,
                zone.zone_id, queue.queue_id, gridId, grid.full_flag,grid.dispatch_flag,
               queue.ration, queue.name, grid.allWeight,

                grid.pallets[0].number, grid.pallets[0].data, grid.pallets[0].weight,
                grid.pallets[0].width, grid.pallets[0].meter,

                grid.pallets[1].number, grid.pallets[1].data, grid.pallets[1].weight,
                grid.pallets[1].width, grid.pallets[1].meter,

                grid.pallets[2].number, grid.pallets[2].data, grid.pallets[2].weight,
                grid.pallets[2].width, grid.pallets[2].meter,

                grid.pallets[3].number, grid.pallets[3].data, grid.pallets[3].weight,
                grid.pallets[3].width, grid.pallets[3].meter,

                grid.count
                );
}



void MyCanvasMaker::reGetGridInfo(int zoneId, int queueId, int gridId)
{
    auto lambda1 = [this, gridId](share_zone_t&zone, share_queue_t&queue, share_grid_t &grid)
    {
        _gridInfoToStr(this->_gridInfoStr, zone, queue, grid, gridId);
        logInfo("");
        this->updateGridInfo();
    };
    _locationData->findGridAndRun(zoneId, queueId, gridId, lambda1);
}

void MyCanvasMaker::startOut(QString ration, int outZoneId, int allweight)
{
    _outStore->startOut(ration.toUtf8().data(), outZoneId, allweight);
    updateCanvas();
    _isOut = 1;
}

void MyCanvasMaker::cancelOut()
{
    logInfo("_outStore->cancelOut");
    _outStore->cancelout();
    _isOut = 0;
}

int MyCanvasMaker::_findInAgv(double x, double y)
{
    int i;
    for (i = 0; i < _agvData->mAgvVector.size(); i++) {
        const AgvData &agv = _agvData->mAgvVector[i];
        double minX = agv.position.x - 2500;
        double maxX = agv.position.x + 2500;
        double minY = agv.position.y - 2500;
        double maxY = agv.position.y + 2500;
        if (!((x >= minX) && (x <= maxX) && (y >= minY) &&(y <= maxY)))
        {
            continue;
        }
        logInfo("MyCanvasMaker::_findInAgv:%d,%d-->%d,%s", agv.AGV_ID,
                agv.c_station, agv.n_station,  ToolFun::ipLong2Str(agv.IPAddress));\
        _agvData->selectAgv(i);
        return 1;
    }
    return 0;
}

int MyCanvasMaker::_findInStation(double x, double y)
{

    foreach (const share_zone_t &zone, _locationData->mZoneVector) {
        _compareCount++;
        //logInfo("AgvCanvasMaker::_findInStation:zone=%d", zone.zone_id);
        if (!((x >= zone.min_x) && (x <= zone.max_x)
                && (y >= zone.min_y) && (y <= zone.max_y)))
        {

            continue;
        }
        for (int i = 0; i < zone.queue_count; i++)
        {
            _compareCount++;

            const share_queue_t &queue = zone.buf[i];
           // logInfo("AgvCanvasMaker::_findInStation:queue=%d", i + zone.queue_start);
           // logInfo("[%lf,%lf][%lf,%lf]", queue.min_x, queue.max_x,
           //         queue.min_y, queue.max_y);
            if (!((x >= queue.min_x) && (x <= queue.max_x)
                    && (y >= queue.min_y) && (y <= queue.max_y)))
            {
                continue;
            }
            for (int j = 0; j < queue.grid_count; j++)
            {
                _compareCount++;
                //logInfo("AgvCanvasMaker::_findInStation:grid=%d", j);
                const share_grid_t &grid = queue.buf[j];
               // logInfo("[%lf,%lf][%lf,%lf]", grid.min_x, grid.max_x,
               //         grid.min_y, grid.max_y);
                if ((x >= grid.min_x) && (x <= grid.max_x)
                        && (y >= grid.min_y) && (y <= grid.max_y))
                {
                    logInfo("(%d,%d,%d),%s%s%d-%d%02d-%d,(%d,%d),flag=(%d,%d)", zone.zone_id, queue.queue_id,
                            j, zone.zoneName2, zone.zoneName, zone.zone_id2,
                            zone.zone_id2, queue.queue_id2 + 1, j + 1,
                            grid.stations[0].id, grid.stations[1].id,
                            grid.full_flag, grid.dispatch_flag);

                    _tipStr.sprintf("%lf,%lf,%s,%s%d-%d%02d-%d,站点:[%d][%d],库位:%d-%d-%d,状态:%d.%d.%d,规格:[%s],重量:[%.4f]",
                            x, y,
                                    //
                            zone.zoneName2, zone.zoneName, zone.zone_id2,
                            zone.zone_id2, queue.queue_id2 + 1, j + 1,
                            grid.stations[0].id, grid.stations[1].id,
                            zone.zone_id, queue.queue_id,    j,
                            grid.full_flag, grid.dispatch_flag,grid.disable,
                            queue.ration, grid.allWeight
                            );

                    _timerTip->start();

                    _gridInfoToStr(_gridInfoStr, zone, queue, grid, j);
                    updateGridInfo();
                    return 1;
                }
            }
        }
    }
    return 0;
}


void MyCanvasMaker::_calculateBorder()
{
    _xMin = 10000000000000;
    _xMax = -10000000000000;
    _yMin = 100000000000000;
    _yMax = -10000000000000;
    QVector<LineData> &lineVector = _mapData->mLineVector;
    foreach (LineData line, lineVector)
    {
        _calculateXy(line.startpoint.x, line.startpoint.y);
        _calculateXy(line.endpoint.x, line.endpoint.y);
    }
    double _xCenter = (_xMax + _xMin) / 2;
    double     _yCenter = (_yMax + _yMin) / 2;
    double    _width = _xMax - _xMin;
    double    _height = _yMax - _yMin;
    updateDefaultPara(_width, _height, _xCenter, _yCenter);
    logInfo("MyCanvasMaker::_calculateBorder:_width=%lf,_height=%lf,Center=%lf,%lf",
            _width, _height, _xCenter, _yCenter);
}

void MyCanvasMaker::_calculateXy(double x, double y)
{
    _xMin = qMin(_xMin, x);
    _xMax = qMax(_xMax, x);

    _yMin = qMin(_yMin, y);
    _yMax = qMax(_yMax, y);
}

